package fnord.network.client;

import java.io.*;
import java.net.Socket;

import fnord.exception.BadPortException;
import fnord.illuminati.Board;
import fnord.network.OrderType;
import fnord.network.server.Player;

public class ClientCommunicatorThread extends Thread {
	
	private Socket _socket;
	private Player _myPlayer;
	private Client _client;
	private ObjectOutputStream _oos;
	
	public ClientCommunicatorThread(Client client, int port, String ipAddress) throws BadPortException, IOException {
		_socket = new Socket(ipAddress, port);
		_client = client;
	}
	
	@Override
	public void run() {
		ObjectInputStream ois = null;
		boolean done = false;
		if(!_socket.isClosed()) {
			try {
				ois = new ObjectInputStream(_socket.getInputStream());
				_myPlayer = (Player) ois.readObject();
				_oos = new ObjectOutputStream(_socket.getOutputStream());
			} catch (IOException e) {
				e.printStackTrace();
			} catch (ClassNotFoundException e) {
				e.printStackTrace();
			}
		}
		while(!_socket.isClosed()) {
			try {
				String s = (String) ois.readObject();
				OrderType ot = OrderType.getTypeFor(s);
				if(ot == OrderType.CHAT) {
					String s1 = (String) ois.readObject();
					System.out.println("Client got the message: " +s1);
					_client.updateChat(s1);
				}
				else if(ot == OrderType.GAME_STATE) {
					Board newBoard = (Board) ois.readObject();
					_client.updateGameState(newBoard);
				}
				else if(ot == OrderType.QUIT) {
					done = true;
				}
			} catch (IOException e) {
				done = true;
			} catch (ClassNotFoundException e) {
				e.printStackTrace();
			}
			finally {
				if(done) {
					try {
						ois.close();
						_oos.close();
						_socket.close();
					} catch (IOException e) {
						e.printStackTrace();
					}
					break;
				}
			}
		}	
	}

	public void sendData(OrderType type, Serializable toSend) throws IOException {
		if(type.sentByClient()) {
			_oos.writeObject(type.getString());
			_oos.flush();
			_oos.writeObject(toSend);
			_oos.flush();
		}
	}
	
	Player getMyPlayer() {
		return _myPlayer;
	}
}
